/**
 * 网络请求封装
 */
import { getToken } from './utils/auth.js'
import config from './config.js'

// 使用配置文件中的API基础URL
const BASE_URL = config.apiBaseUrl

// 请求函数
export const request = (options) => {
  // 构建完整URL
  let fullUrl = '';
  if (options.url.startsWith('http')) {
    // 如果是完整的URL，直接使用
    fullUrl = options.url;
  } else {
    // 否则拼接BASE_URL
    if (options.url.startsWith('/')) {
      fullUrl = BASE_URL + options.url;
    } else {
      fullUrl = BASE_URL + '/' + options.url;
    }
  }
  
  // 获取token
  const token = getToken();
  
  // 构建请求头
  const header = {
    'Content-Type': 'application/json',
    'X-Requested-With': 'XMLHttpRequest', // 帮助某些服务器识别Ajax请求
    ...options.header
  };
  
  // 添加token
  if (token) {
    header['Authorization'] = `Bearer ${token}`;
  }
  
  // 打印请求信息，便于调试
  console.log('发起请求:', {
    url: fullUrl,
    baseUrl: BASE_URL,
    originalUrl: options.url,
    method: options.method || 'GET',
    data: options.data || {}
  });
  
  // 发送请求
  return new Promise((resolve, reject) => {
    uni.request({
      url: fullUrl,
      method: options.method || 'GET',
      data: options.data || {},
      header: header,
      timeout: config.timeout || 10000,
      withCredentials: true, // 允许跨域请求携带凭证
      
      // 请求成功回调
      success: (res) => {
        console.log('请求响应状态码:', res.statusCode);
        try {
          // 尝试记录响应数据，但可能太大而无法完整打印
          console.log('请求响应数据:', typeof res.data === 'object' ? 
            JSON.stringify(res.data).substring(0, 500) + (JSON.stringify(res.data).length > 500 ? '...(截断)' : '') : 
            res.data);
        } catch (e) {
          console.log('响应数据太大无法打印');
        }
        
        // 处理CORS预检请求响应
        if (res.statusCode === 204 && options.method === 'OPTIONS') {
          resolve({ code: 0, data: null, msg: 'CORS预检成功' });
          return;
        }
        
        // 处理HTTP状态码
        if (res.statusCode === 404) {
          reject({
            code: 404,
            msg: '请求的资源不存在',
            error: res.data
          });
          return;
        }
        
        if (res.statusCode === 401) {
          // token过期，需要重新登录
          uni.showToast({
            title: '登录已过期，请重新登录',
            icon: 'none'
          });
          
          // 清除本地token
          uni.removeStorageSync('xuetang_token');
          uni.removeStorageSync('xuetang_user_info');
          
          // 跳转到登录页
          setTimeout(() => {
            uni.navigateTo({
              url: '/pages/login/index'
            });
          }, 1500);
          
          reject({
            code: 401,
            msg: '登录已过期',
            error: res.data
          });
          return;
        }
        
        if (res.statusCode === 403) {
          reject({
            code: 403,
            msg: '没有权限访问该资源',
            error: res.data
          });
          return;
        }
        
        if (res.statusCode >= 500) {
          reject({
            code: res.statusCode,
            msg: '服务器错误，请稍后再试',
            error: res.data
          });
          return;
        }
        
        if (res.statusCode === 200) {
          try {
            // 确保响应数据是一个对象
            let responseData;
            
            // 处理各种可能的响应数据格式
            if (typeof res.data === 'string') {
              try {
                responseData = JSON.parse(res.data);
              } catch (parseError) {
                console.error('响应数据解析失败:', parseError);
                console.log('原始响应字符串:', res.data);
                // 如果无法解析，可能是普通文本或HTML
                responseData = {
                  code: 0,
                  data: res.data,
                  msg: '响应不是JSON格式'
                };
              }
            } else {
              // 已经是对象
              responseData = res.data;
            }
            
            if (responseData.code === 401) {
              // token过期，需要重新登录
              uni.showToast({
                title: '登录已过期，请重新登录',
                icon: 'none'
              });
              
              // 清除本地token
              uni.removeStorageSync('xuetang_token');
              uni.removeStorageSync('xuetang_user_info');
              
              // 跳转到登录页
              setTimeout(() => {
                uni.navigateTo({
                  url: '/pages/login/index'
                });
              }, 1500);
              
              reject(responseData);
            } else {
              resolve(responseData);
            }
          } catch (e) {
            console.error('解析响应数据失败:', e);
            console.error('原始响应数据类型:', typeof res.data);
            try {
              console.error('原始响应数据片段:', typeof res.data === 'string' ? 
                res.data.substring(0, 100) : 
                JSON.stringify(res.data).substring(0, 100));
            } catch (logError) {
              console.error('无法记录原始响应数据');
            }
            
            reject({
              code: -2,
              msg: '解析响应数据失败: ' + e.message,
              error: e.message
            });
          }
        } else {
          // 增强错误日志，输出详细信息
          console.error('请求失败，状态码:', res.statusCode);
          console.error('请求URL:', fullUrl);
          console.error('请求方法:', options.method || 'GET');
          console.error('请求数据:', JSON.stringify(options.data || {}));
          console.error('请求头:', JSON.stringify(header));
          try {
            console.error('响应数据:', typeof res.data === 'object' ? JSON.stringify(res.data) : res.data);
          } catch (e) {
            console.error('响应数据太大或格式错误无法打印');
          }
          
          uni.showToast({
            title: res.data?.message || res.data?.msg || `请求失败，状态码: ${res.statusCode}`,
            icon: 'none'
          });
          reject(res.data || { msg: `网络请求错误，状态码：${res.statusCode}` });
        }
      },
      fail: (err) => {
        console.error('请求失败:', err);
        console.error('请求URL:', fullUrl);
        console.error('请求方法:', options.method || 'GET');
        try {
          console.error('请求数据:', JSON.stringify(options.data || {}));
        } catch (e) {
          console.error('请求数据无法序列化:', options.data);
        }
        
        // 区分不同类型的错误
        let errorMsg = '网络请求失败';
        if (err.errMsg.includes('timeout')) {
          errorMsg = '请求超时，请检查网络';
        } else if (err.errMsg.includes('Failed to connect')) {
          errorMsg = '无法连接到服务器，请检查网络';
        }
        
        uni.showToast({
          title: errorMsg,
          icon: 'none'
        });
        reject({
          code: -1,
          msg: errorMsg,
          error: err
        });
      }
    });
  });
}

// 请求方法
const requestMethods = {
  /**
   * GET请求
   */
  get(url, data = {}, options = {}) {
    return request({
      url,
      data,
      method: 'GET',
      ...options
    });
  },
  
  /**
   * POST请求
   */
  post(url, data = {}, options = {}) {
    return request({
      url,
      data,
      method: 'POST',
      ...options
    });
  },
  
  /**
   * PUT请求
   */
  put(url, data = {}, options = {}) {
    return request({
      url,
      data,
      method: 'PUT',
      ...options
    });
  },
  
  /**
   * DELETE请求
   */
  delete(url, data = {}, options = {}) {
    return request({
      url,
      data,
      method: 'DELETE',
      ...options
    });
  }
};

export default requestMethods; 